package org.filetransfer.file_transfer_java_backend.service;
import com.sun.management.OperatingSystemMXBean;
import jakarta.annotation.Nullable;
import org.filetransfer.file_transfer_java_backend.model.FileCategoryModel;
import org.filetransfer.file_transfer_java_backend.model.ServiceFileInfoModel;
import org.filetransfer.file_transfer_java_backend.model.ServiceShareInfoModel;
import org.filetransfer.file_transfer_java_backend.utils.DirectorySizeCalculatorNIO;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.lang.management.ManagementFactory;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.List;
import java.util.Optional;
@Service
public class StatisticService {
    @Autowired
    private FileUploadService fileUploadService;
    // 获取服务器存储目录剩余空间
    public long getStorageFreeSpace() {
        var dir = fileUploadService.getConfigFileStorageDir();
        var dirPath = Path.of(dir);
        try {
            var fileStore = Files.getFileStore(dirPath);
            return fileStore.getUsableSpace();
        } catch (IOException e) {
            // 获取失败
            return -1;
        }
    }
    // 获取服务器存储目录已使用空间
    public long getStorageUsedSpace() {
        var dir = fileUploadService.getConfigFileStorageDir();
        var dirPath = Path.of(dir);
        try {
            //获取存储目录下所有文件的大小合（包括子目录）
            return DirectorySizeCalculatorNIO.getDirectorySize(dirPath);
        } catch (IOException e) {
            // 获取失败
            return -1;
        }
    }
    // 获取服务器负载信息（cpu、内存、磁盘io等）（仅展示百分比）
    public record ServerOverloadInfo(double cpuUsage, double memoryUsage) {}
    public ServerOverloadInfo getServerOverloadInfo() {
        var osBean = ManagementFactory.getPlatformMXBean(OperatingSystemMXBean.class);
        // CPU 使用率
        double cpuUsage = osBean.getCpuLoad() * 100;
        // 内存使用率
        long totalMemory = osBean.getTotalMemorySize();
        long freeMemory = osBean.getFreeMemorySize();
        double memoryUsage = ((double) (totalMemory - freeMemory) / totalMemory) * 100;
        return new ServerOverloadInfo(cpuUsage, memoryUsage);
    }
    //    // 获取服务器网络负载信息 (linux)
//    public record ServerNetworkOverloadInfo(long uploadSpeedBytesPerSecond, long downloadSpeedBytesPerSecond) {}
//    public ServerNetworkOverloadInfo getServerNetworkOverloadInfo() {
//        long initialTx = getNetworkData("/sys/class/net/eth0/statistics/tx_bytes");
//        long initialRx = getNetworkData("/sys/class/net/eth0/statistics/rx_bytes");
//        try {
//            Thread.sleep(1000);
//        } catch (InterruptedException e) {
//            e.printStackTrace();
//        }
//        long finalTx = getNetworkData("/sys/class/net/eth0/statistics/tx_bytes");
//        long finalRx = getNetworkData("/sys/class/net/eth0/statistics/rx_bytes");
//        long uploadSpeed = finalTx - initialTx;
//        long downloadSpeed = finalRx - initialRx;
//        return new ServerNetworkOverloadInfo(uploadSpeed, downloadSpeed);
//    }
//    private long getNetworkData(String path) {
//        try {
//            return Long.parseLong(Files.readString(Paths.get(path)).trim());
//        } catch (Exception e) {
//            e.printStackTrace();
//            return 0;
//        }
//    }
    @Autowired
    private FileService fileService;    public Optional<ServiceFileInfoModel> getServiceFileStatistics(@Nullable Integer dayOfBefore) {
        return fileService.getStatistics(dayOfBefore);
    }
    
    public Optional<ServiceFileInfoModel> getServiceFileStatisticsByUser(@Nullable Integer dayOfBefore, Long userId) {
        return fileService.getStatisticsByUser(dayOfBefore, userId);
    }
    
    @Autowired
    private ShareItemService shareItemService;
    public Optional<ServiceShareInfoModel> getServiceShareStatistics(@Nullable Integer dayOfBefore) {
        return shareItemService.getStatistics(dayOfBefore);
    }
    
    public Optional<ServiceShareInfoModel> getServiceShareStatisticsByUser(@Nullable Integer dayOfBefore, Long userId) {
        return shareItemService.getStatisticsByUser(dayOfBefore, userId);
    }
    
    public List<FileCategoryModel> getFileCategoryInfo() {
        return fileService.getFileCategoryStatistics();
    }
    
    public List<FileCategoryModel> getFileCategoryInfoByUser(Long userId) {
        return fileService.getFileCategoryStatisticsByUser(userId);
    }
}
